Skip to content

fix: avoid 502 on long-running agents via non-blocking + polling - #8

Open
LeoMartin-30 wants to merge 3 commits into
dust-tt:masterfrom
LeoMartin-30:fix/non-blocking-polling
Open

fix: avoid 502 on long-running agents via non-blocking + polling#8
LeoMartin-30 wants to merge 3 commits into
dust-tt:masterfrom
LeoMartin-30:fix/non-blocking-polling

Conversation

@LeoMartin-30

Copy link
Copy Markdown

Summary

Switches the Talk To Agent operation from blocking: true to non-blocking POST + polling on GET /conversations/{id}. Fixes the 502 Bad Gateway that systematically happens with agents that take more than ~30 s (Jira / Slack / Google Docs / MCP tool calls), reported in #7.

Adds a small set of optional fields and surfaces richer info in the output, all backward-compatible (default behavior still produces an agentMessage).

Closes #7.

What changed

Behavior

  • POST /conversations no longer sets blocking: true / skipToolsValidation: true — the call returns immediately with the conversation sId.
  • The node then polls GET /conversations/{id} until the latest agent_message reaches a terminal status (succeeded, failed, cancelled) or the deadline is hit.
  • On failed/cancelled, throws with the agent error message + the conversation URL for inspection.

New Additional Fields (all optional)

Field Default Use
Wait For Completion true Off = return immediately with just conversationId and let the user poll themselves.
Poll Interval (Ms) 1500 Time between poll attempts.
Max Wait (Ms) 120000 Hard ceiling on total wait.
Full Name "" New context.fullName field for Langfuse attribution.
Include Generated File Content true When on, downloads each file the agent generates and inlines it.
Max Generated File Size (Bytes) 10_000_000 Per-file size ceiling — over this, content is omitted and tooLarge: true is set.

Output additions

  • conversationId — useful for follow-up messages or conversationTitle.
  • chainOfThought — reasoning trace for thinking-capable models, null otherwise.
  • conversationTitle — auto-generated title once the agent finishes.
  • rawConversation — full conversation object for downstream extraction.
  • generatedFiles[] — every file produced during the run (across all tool calls), deduped by fileId, with metadata + inlined content / contentBase64 (controlled by Include Generated File Content). Empty array when the agent produces none.

Test plan

  • Built locally with npm run build + npm run lint + .eslintrc.prepublish.js lint — clean.
  • Installed into ~/.n8n/custom via tarball, loaded by CustomDirectoryLoader, confirmed via n8n export:nodes (Dust / CUSTOM.dust / v1 with all 9 Additional Fields in alphabetical order).
  • Manually executed against DATA_WeeklyNotesRewriter (agent that calls Jira / Slack / Google Docs and previously 502'd): node now waits ~3 min and returns the markdown final answer + 3 generated Jira extract files with inlined content.
  • Reviewer test: agent that finishes quickly (e.g. Internal Prompt Writer) — should not regress.
  • Reviewer test: agent that throws — should surface the error message + conversation URL.
  • Reviewer test: Wait For Completion: false — should return immediately with conversationId.

The current Talk-to-Agent flow POSTs with `blocking: true`, which holds
the HTTP connection open until the agent finishes. Agents that call out
to slow tools (Jira, Slack, Google Docs, MCP servers...) routinely take
>30s and the upstream gateway drops the connection, surfacing as
502 Bad Gateway in n8n.

Switch to the pattern used by Dust's own clients: POST returns
immediately with the conversation sId, then we poll GET
/conversations/{id} until the latest agent_message reaches a terminal
status (succeeded, failed, cancelled) or the max-wait deadline elapses.

New Additional Fields:
- Wait For Completion (default true) — turn off to return immediately
  with just { conversationId, conversationUrl, userMessage }
- Poll Interval (Ms) (default 1500)
- Max Wait (Ms) (default 120000)
- Full Name — exposed on the message context for Langfuse attribution

Output shape is preserved (`agentMessage` + `conversationUrl` +
`userMessage`) and a new `conversationId` field is added so downstream
nodes can run follow-ups or open the conversation in the Dust UI.

Refs dust-tt#7
Once the agent succeeds, surface three additional fields alongside
`agentMessage`:

- `chainOfThought` — reasoning trace for thinking-capable models
  (Sonnet/Opus). Useful to render a "thinking" preview before the
  final answer or to debug agent runs.
- `conversationTitle` — auto-generated title Dust attaches once the
  agent completes. Handy when archiving conversations downstream.
- `rawConversation` — the full conversation object including
  `content`, `actions`, `citations`, and `generatedFiles`. Lets
  workflows extract specific tool outputs (e.g. generated file IDs,
  per-action params) without making a second GET call.

All three are additive and backward-compatible with the existing
`agentMessage` / `conversationId` / `conversationUrl` / `userMessage`
fields.
When an agent generates files during its run — Jira extracts, CSV/HTML
exports, visualizations attached to tool calls — they were buried
inside `rawConversation.content[*].actions[*].generatedFiles` and
required custom n8n expressions to dig out.

Aggregate them into a top-level `generatedFiles` array on the output,
deduplicated by `fileId`, with each entry carrying its title, content
type, snippet, download URL, source tool name and action sId.

When the new `Include Generated File Content` field is on (default
true), the node also downloads each file via
`GET /api/w/{wId}/files/{fileId}?action=download` and inlines:

- `content` (UTF-8 string) for textual content types — text/*, JSON,
  XML, HTML, CSV, Markdown, YAML.
- `contentBase64` for binary content.
- `tooLarge: true` for files exceeding the per-file cap (default
  10 MB, configurable via `Max Generated File Size (Bytes)`).
- `downloadError` if a single fetch fails, without breaking the
  whole node run.

Backward-compatible: when an agent produces no files, the output
array is simply empty.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Bad Gateaway - Request failed with status code 502

2 participants